package cn.chenxinjie.hrm.config;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableResourceServer;
import org.springframework.security.oauth2.config.annotation.web.configuration.ResourceServerConfigurerAdapter;
import org.springframework.security.oauth2.config.annotation.web.configurers.ResourceServerSecurityConfigurer;
import org.springframework.security.oauth2.provider.token.RemoteTokenServices;
import org.springframework.security.oauth2.provider.token.ResourceServerTokenServices;
import org.springframework.security.oauth2.provider.token.TokenStore;
import org.springframework.security.oauth2.provider.token.store.JwtAccessTokenConverter;
import org.springframework.security.oauth2.provider.token.store.JwtTokenStore;

/**
 * @author 陈鑫杰
 * @date 2022/3/22 12:49
 */
@EnableResourceServer // 开启资源服务器
@Configuration
@EnableGlobalMethodSecurity(prePostEnabled = true)
public class HrmResourceCommonConfig extends ResourceServerConfigurerAdapter {
    @Value("${oauth.resourceId}")
    private String resourceId;

    /**
     * @param resources
     * @throws Exception
     */
    @Override
    public void configure(ResourceServerSecurityConfigurer resources) throws Exception {
        // 设置我们资源的名称
        resources.resourceId(resourceId)
                // 使用tokenStore的方式
                .tokenStore(getJwtTokenStore());
        // 使用tokenService的方式 (需要调用远程服务)
        //resources.tokenServices(resourceServerTokenServices());
    }

    //@Bean
    public ResourceServerTokenServices resourceServerTokenServices(){
        // 远程调用的tokenService
        RemoteTokenServices tokenService = new RemoteTokenServices();

        return tokenService;

        /* 这是使用远程调用认证授权服务获取授权信息的方法
        // 设置调用的获取授权的服务的url
        tokenService.setCheckTokenEndpointUrl("http://localhost:4010/oauth/check_token");
        // 设置客户端的账号密码
        tokenService.setClientId("admin");
        tokenService.setClientSecret("1");
        return tokenService;
        */
    }

    /**
     * 获取jwtTokenStore
     * @return
     */
    @Bean
    public TokenStore getJwtTokenStore() {
        JwtTokenStore jwtTokenStore = new JwtTokenStore(jwtAccessTokenConverter());
        return jwtTokenStore;
    }

    private static final String key = "chenxinjie";
    /**
     * jwt token转换器
     * @return
     */
    @Bean
    public JwtAccessTokenConverter jwtAccessTokenConverter() {
        JwtAccessTokenConverter jwtAccessTokenConverter = new JwtAccessTokenConverter();
        // 设置密钥 (盐值)
        jwtAccessTokenConverter.setSigningKey(key);
        return jwtAccessTokenConverter;
    }

    /**
     * http安全配置
     *
     * @param http
     * @throws Exception
     */
    @Override
    public void configure(HttpSecurity http) throws Exception {
        // 校验scope必须为hrm,对应认证服务的客户端详情配置的clientId
        http.authorizeRequests()
                .antMatchers("/**").permitAll()
                //.antMatchers("/**").access("#oauth2.hasScope('hrm')")
                // 关闭跨域伪造检查
                .and().csrf().disable()
                // 把session设置为无状态，意思是使用了token，那么session不再做数据的记录
                .sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS);
    }
}
